﻿using System;
using System.Collections.Generic;
using Autodesk.Revit.DB;
using Autodesk.Revit.DB.Electrical;
using YArchitech.Revit.Electric.Common;

namespace HYCableTrayConnection
{
	internal class HYAutomaticConnection
	{
		public bool NewAutomaticConnect(IList<CableTray> cableTrays)
		{
			bool result = true;
			if (cableTrays == null || cableTrays.Count < 2)
			{
				throw new MyException("请选择2到4根桥架");
			}
			Document document = cableTrays[0].Document;
			if (!Common.IsSameCableTrayType(document, cableTrays))
			{
				throw new MyException("桥架的类型不一致");
			}
			HYCableTrayConnect hyCableTrayConnect = new HYCableTrayConnect();
			switch (cableTrays.Count)
			{
			case 1:
				throw new MyException("请选择2到4根桥架");
			case 2:
				result = this.SelectTwoBridge(document, hyCableTrayConnect, cableTrays);
				break;
			case 3:
				result = this.SelectThreeBridge(document, hyCableTrayConnect, cableTrays);
				break;
			case 4:
				result = this.SelectFourBridge(hyCableTrayConnect, cableTrays);
				break;
			}
			return result;
		}

		private bool SelectTwoBridge(Document doc, HYCableTrayConnect hyCableTrayConnect, IList<CableTray> cableTrays)
		{
			bool flag = false;
			int integerValue = cableTrays[0].Id.IntegerValue;
			int integerValue2 = cableTrays[1].Id.IntegerValue;
			try
			{
				flag = new HYPlanarConnection().NewPlanarConnection(cableTrays);
			}
			catch (Exception)
			{
			}
			if (flag)
			{
				return flag;
			}
			try
			{
				cableTrays = this.GetSelCableTrays(doc, integerValue, integerValue2);
				IList<CableTray> cableTrays2 = this.SetSplitBridge(false, cableTrays, 2);
				flag = hyCableTrayConnect.NewCrossFitting(cableTrays2);
			}
			catch (Exception)
			{
			}
			if (flag)
			{
				return flag;
			}
			try
			{
				cableTrays = this.GetSelCableTrays(doc, integerValue, integerValue2);
				IList<CableTray> cableTrays3 = this.SetSplitBridge(true, cableTrays, 2);
				flag = hyCableTrayConnect.NewTeeFitting(cableTrays3);
			}
			catch (Exception)
			{
			}
			if (flag)
			{
				return flag;
			}
			cableTrays = this.GetSelCableTrays(doc, integerValue, integerValue2);
			flag = hyCableTrayConnect.NewElbowFitting(cableTrays);
			return flag;
		}

		private bool SelectThreeBridge(Document doc, HYCableTrayConnect hyCableTrayConnect, IList<CableTray> cableTrays)
		{
			bool flag = false;
			int integerValue = cableTrays[0].Id.IntegerValue;
			int integerValue2 = cableTrays[1].Id.IntegerValue;
			int integerValue3 = cableTrays[2].Id.IntegerValue;
			try
			{
				IList<CableTray> cableTrays2 = this.SetSplitBridge(false, cableTrays, 3);
				flag = hyCableTrayConnect.NewCrossFitting(cableTrays2);
			}
			catch (Exception)
			{
			}
			if (flag)
			{
				return flag;
			}
			cableTrays = this.GetSelCableTrays(doc, integerValue, integerValue2, integerValue3);
			flag = hyCableTrayConnect.NewTeeFitting(cableTrays);
			return flag;
		}

		private bool SelectFourBridge(HYCableTrayConnect hyCableTrayConnect, IList<CableTray> cableTrays)
		{
			return hyCableTrayConnect.NewCrossFitting(cableTrays);
		}

		private IList<CableTray> SetSplitBridge(bool isTee, IList<CableTray> cableTray, int number = 2)
		{
			List<CableTray> list = new List<CableTray>();
			HYCableTray<CableTray> hycableTray = new HYCableTray<CableTray>(cableTray[0]);
			HYCableTray<CableTray> hycableTray2 = new HYCableTray<CableTray>(cableTray[1]);
			if (isTee)
			{
				if (this.JudgeSplitBridge(hycableTray, hycableTray2))
				{
					list.Add(cableTray[0]);
					list.Add(cableTray[0]);
					list.Add(cableTray[1]);
				}
				else
				{
					list.Add(cableTray[1]);
					list.Add(cableTray[1]);
					list.Add(cableTray[0]);
				}
				return list;
			}
			if (number == 2)
			{
				list.Add(cableTray[0]);
				list.Add(cableTray[0]);
				list.Add(cableTray[1]);
				list.Add(cableTray[1]);
				return list;
			}
			HYCableTray<CableTray> hycableTray3 = new HYCableTray<CableTray>(cableTray[2]);
			if (this.JudgeSplitBridge(hycableTray, hycableTray2) || this.JudgeSplitBridge(hycableTray, hycableTray3))
			{
				list.Add(hycableTray.CableTray);
				list.Add(hycableTray.CableTray);
				list.Add(hycableTray2.CableTray);
				list.Add(hycableTray3.CableTray);
			}
			else if (this.JudgeSplitBridge(hycableTray2, hycableTray3) || this.JudgeSplitBridge(hycableTray2, hycableTray))
			{
				list.Add(hycableTray2.CableTray);
				list.Add(hycableTray2.CableTray);
				list.Add(hycableTray.CableTray);
				list.Add(hycableTray3.CableTray);
			}
			else
			{
				list.Add(hycableTray3.CableTray);
				list.Add(hycableTray3.CableTray);
				list.Add(hycableTray.CableTray);
				list.Add(hycableTray2.CableTray);
			}
			return list;
		}

		private bool JudgeSplitBridge(HYCableTray<CableTray> ct1, HYCableTray<CableTray> ct2)
		{
			XYZ lineProject = ct1.GetLineProject(ct2.EndXYZ);
			bool result = false;
			XYZ xyz = (ct1.StartXYZ - lineProject).Normalize();
			XYZ xyz2 = (ct1.EndXYZ - lineProject).Normalize();
			if (xyz.IsAlmostEqualTo(-xyz2, 0.01))
			{
				result = true;
			}
			return result;
		}

		private List<CableTray> GetSelCableTrays(Document doc, int id, int id1)
		{
			List<CableTray> list = new List<CableTray>();
			IEnumerable<Element> enumerable = RevitFilter.GetElementsOfType(doc, typeof(CableTray)).ToElements();
			int num = 0;
			foreach (Element element in enumerable)
			{
				CableTray cableTray = element as CableTray;
				if (cableTray.Id.IntegerValue == id)
				{
					list.Add(cableTray);
					num++;
				}
				else if (cableTray.Id.IntegerValue == id1)
				{
					list.Add(cableTray);
					num++;
				}
				else if (num == 2)
				{
					break;
				}
			}
			return list;
		}

		private List<CableTray> GetSelCableTrays(Document doc, int id, int id1, int id2)
		{
			List<CableTray> list = new List<CableTray>();
			IEnumerable<Element> enumerable = RevitFilter.GetElementsOfType(doc, typeof(CableTray)).ToElements();
			int num = 0;
			foreach (Element element in enumerable)
			{
				CableTray cableTray = element as CableTray;
				if (cableTray.Id.IntegerValue == id)
				{
					list.Add(cableTray);
					num++;
				}
				else if (cableTray.Id.IntegerValue == id1)
				{
					list.Add(cableTray);
					num++;
				}
				else if (cableTray.Id.IntegerValue == id2)
				{
					list.Add(cableTray);
					num++;
				}
				else if (num == 3)
				{
					break;
				}
			}
			return list;
		}
	}
}
